package cn.truistic.enmicromsg.main.model;

import android.content.Context;
import android.util.Log;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONException;
import com.alibaba.fastjson.TypeReference;
import com.squareup.okhttp.Call;
import com.squareup.okhttp.FormEncodingBuilder;
import com.squareup.okhttp.OkHttpClient;
import com.squareup.okhttp.Request;
import com.squareup.okhttp.RequestBody;
import com.squareup.okhttp.Response;

import net.sqlcipher.database.SQLiteDatabase;

import org.litepal.crud.DataSupport;

import java.io.IOException;
import java.util.List;

import cn.truistic.enmicromsg.Message;
import cn.truistic.enmicromsg.bean.CodeBean;
import cn.truistic.enmicromsg.bean.Contact;
import cn.truistic.enmicromsg.common.util.BaseUrl;
import cn.truistic.enmicromsg.common.util.CursorUtils;
import cn.truistic.enmicromsg.common.util.PreferenceHelper;
import cn.truistic.enmicromsg.common.util.SharedPerfUtil;
import cn.truistic.enmicromsg.main.MainMVP;

/**
 * HomeModel
 */
public class HomeModel implements MainMVP.IHomeModel {

    private Context context;
    private MainMVP.IHomePresenter homePresenter;
    private int part = 0; //轮询发送的次数
    private int courrPart = 0; //当前发送的次数
    private int courrNumber = 0; //聊天消息的数量
    private int courrContactNumber = 0; //联系人的数量
    private List<Contact> allNews; //联系人的集合
    private List<Message> messagesAll; //聊天消息的集合
    int pointsDataLimit = 300; //限制条数

    public HomeModel(MainMVP.IHomePresenter homePresenter, Context context) {
        this.homePresenter = homePresenter;
        this.context = context;
    }

    @Override
    public MainMVP.IHomeView.State getState(MainMVP.IHomeView.Progress progress) {
        switch (SharedPerfUtil.getState(context, progress)) {
            case 0:
                return MainMVP.IHomeView.State.UNDETECTED;
            case 1:
                return MainMVP.IHomeView.State.DETECTING;
            case 2:
                return MainMVP.IHomeView.State.TRUE;
            case 3:
                return MainMVP.IHomeView.State.FALSE;
        }
        return MainMVP.IHomeView.State.UNDETECTED;
    }

    @Override
    public void saveState(MainMVP.IHomeView.Progress progress, MainMVP.IHomeView.State state) {
        int stateInt = 0;
        switch (state) {
            case UNDETECTED:
                stateInt = 0;
                break;
            case DETECTING:
                stateInt = 1;
                break;
            case TRUE:
                stateInt = 2;
                break;
            case FALSE:
                stateInt = 3;
                break;
        }
        SharedPerfUtil.saveProgressState(context, progress, stateInt);
    }

    @Override
    public int getDbNum() {
        return SharedPerfUtil.getDbNum(context);
    }

    @Override
    public void saveDbNum(int num) {
        SharedPerfUtil.saveDbNum(context, num);
    }

    @Override
    public String getDbPwd() {
        return SharedPerfUtil.getDbPwd(context);
    }

    @Override
    public void saveDbPwd(String pwd) {
        SharedPerfUtil.savedbPwd(context, pwd);
    }

    // 打开聊天记录表
    @Override
    public void openMessageTable(SQLiteDatabase db) {
        part = 0;
        courrPart = 0;
        int erroCode = CursorUtils.openMessageTable(db, homePresenter.getUinStr());
        try {
            if (erroCode == 1) {
                //处理上传
                messagesAll = DataSupport.findAll(Message.class);
                int listSize = messagesAll.size();
                int count = PreferenceHelper.getInt("MessageNumber", 0);  //第一次 0  第二次 140
                if (count != 0 && count < listSize && null != messagesAll) {
                    Log.e("TAG", "新增聊天消息");
                    //新增聊天消息
                    List<Message> NewsList = null;
                    if (PreferenceHelper.getBoolean("partUploadMessageFailure", false)) {
                        NewsList = messagesAll.subList( 0 , listSize );
                    } else {
                        NewsList = messagesAll.subList( count , listSize );
                    }
                    onMessageUpload(NewsList);
                } else if (count != 0 && count >= listSize && null != messagesAll) {
                    Log.e("TAG", "聊天消息数量不变");
                    //聊天消息数量不变
                    if (PreferenceHelper.getBoolean("partUploadMessageFailure", false)) {
                        //判断第一次是否上传失败 ，如果上传失败，则下一次进入从新上传
                        onMessageUpload(messagesAll);
                    }
                } else if (count == 0 && listSize > 0 && null != messagesAll) {
                    //第一次上传  数据量大的情况需要分批上传
                    int size = listSize;
                    //判断是否有必要分批
                    courrNumber = listSize;
                    if (pointsDataLimit < size) {
                        part = size / pointsDataLimit; //分批数
                        for ( int i = 0; i <= part; i++ ) {
                            Log.e("TAG", "共有 ： " + size + "条，！" + " 分为 ：" + i + "批" + "---->" + courrNumber);
                            List<Message> listPage;
                            if (courrNumber > pointsDataLimit) {
                                listPage = messagesAll.subList(0, pointsDataLimit);
                            } else {
                                listPage = messagesAll.subList(0, courrNumber);
                            }
                            onMessageUpload(listPage);
                        }
                    } else {
                        //不足300条数据
                        Log.e("TAG", "共有 ： " + size + "条，！" + " 分为 ：" + part + "批" + "---->" + courrNumber);
                        onMessageUpload(messagesAll);
                    }
                }
                //保存数量
                PreferenceHelper.commitInt("MessageNumber", listSize);
            } else {
                if (homePresenter != null) {
                    homePresenter.onMessageFailure(courrPart);
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
            if (homePresenter != null) {
                homePresenter.onMessageFailure(courrPart);
            }
        }
    }

    // 打开联系人表
    @Override
    public void openContactTable(SQLiteDatabase db) {
        part = 0;
        courrPart = 0;
        // verifyFlag!=0：公众号等类型 type=33：微信功能 type=2：未知 type=4：非好友
        // 一般公众号原始ID开头都是gh_
        // 群ID的结尾是@chatroom
        int erroCode = CursorUtils.openContactTable(db); //把数据插入本地数据库
        try {
            if (erroCode == 1) {
                //获取成功
                allNews = DataSupport.findAll(Contact.class);
                int listSize = allNews.size();
                int count = PreferenceHelper.getInt("ContactNumber", 0);  //第一次 0  第二次 140
                if (count != 0 && count < listSize && null != allNews) {
                    Log.e("TAG", "新增联系人");
                    //新增联系人
                    List<Contact> NewsList;
                    if (PreferenceHelper.getBoolean("partUploadFailure", false)) {
                        NewsList = allNews.subList(0, listSize);
                    } else {
                        NewsList = allNews.subList(count, listSize);
                    }
                    onUploadData( NewsList.size() , NewsList );
                } else if (count != 0 && count >= listSize && null != allNews ) {
                    Log.e("TAG", "联系人数量不变");
                    //判断是否上传失败 ，如果上传失败，则下一次进入从小上传
                    if (PreferenceHelper.getBoolean("partUploadFailure", false)) {
                        onContactsUpload(allNews);
                    }
                    homePresenter.showContactUnchanged();
                } else if (count == 0 && listSize > 0 && null != allNews) {
                    //第一次上传  数据量大的情况需要分批上传
                    onUploadData( listSize , allNews );
                }
                //保存数量
                PreferenceHelper.commitInt("ContactNumber", listSize);
            } else {
                if (homePresenter != null) {
                    homePresenter.onFailure(courrPart);
                }
            }
        } catch (Exception e) {
            if (homePresenter != null) {
                homePresenter.onFailure(courrPart);
            }
        }
    }

    //分批上传联系人
    private void onUploadData(int listSize, List<Contact> allNews) {
        if (pointsDataLimit < listSize) {
            part = listSize / pointsDataLimit; //分批数
            Log.e("TAG", part + "---->");
            courrContactNumber = listSize;
            for (int i = 0; i <= part; i++) {
                Log.e("TAG", "共有 ： " + listSize + "条，！" + " 分为 ：" + i + "批" + "---->" + courrContactNumber);
                List<Contact> listPage;
                if (courrContactNumber > pointsDataLimit) {
                    listPage = allNews.subList(0, pointsDataLimit);
                } else {
                    listPage = allNews.subList(0, courrContactNumber);
                }
                onContactsUpload(listPage);
            }
        } else {
            //不足300条数据
            onContactsUpload(allNews);
        }
    }


    // 打开用户信息表
    @Override
    public int openUserInfoTable(SQLiteDatabase db) {
        // 这个数组是保存用户信息，第一次拿到的是账号，第二次是昵称
        return CursorUtils.openUserInfoTable(db);
    }


    //上传到服务器
    @Override
    public void onContactsUpload(List<Contact> list) {
        try {
            OkHttpClient mOkHttpClient = new OkHttpClient();
            final String requestUrl = "http://" + BaseUrl.BASE_IP + "/Dfriend/IndexWx";
            Log.i("INFO", "Request Url: " + requestUrl);
            //.replace("\\", "")
            String json = list.toString();
            Log.e("TAG", json);
            RequestBody requestBody = new FormEncodingBuilder()
                    .add("e.JsonStr", json)
                    .build();
            final Request request = new Request.Builder()
                    .url(requestUrl)
                    .post(requestBody)// post json提交
                    .build();
            Call call = mOkHttpClient.newCall(request);
            Response response = call.execute();
            CodeBean entity;
            String jsonContent = response.body().string();
            Log.e("TAG", jsonContent);
            entity = JSON.parseObject(jsonContent, new TypeReference<CodeBean>() {});
            if (response.isSuccessful() && entity.getCode() == 0 ) {
                Log.e("TAG", "上传成功...");
                if (part == 0) {
                    if (PreferenceHelper.getBoolean("partUploadFailure", false)) {
                        PreferenceHelper.commitBoolean("partUploadFailure", false);
                    }
                }
            } else {
                Log.e("TAG", jsonContent);
                if ( homePresenter != null ) {
                     homePresenter.onFailure(courrPart);
                }
                if ( part == 0 ) {
                    PreferenceHelper.commitBoolean("partUploadFailure", true);
                }
            }
        } catch (Exception e) {
            if (part == 0) {
                PreferenceHelper.commitBoolean("partUploadFailure", true);
            }
            Log.e("TAG", e.getMessage());
        } finally {
            if (courrPart < part && part != 0) {
                allNews.subList(0, pointsDataLimit).clear();
                courrContactNumber = allNews.size();
                courrPart++;
            } else {
                if (homePresenter != null && courrPart == part) {
                    homePresenter.uploadResponse();
                }
            }
        }
    }

    //上传聊天记录到服务器
    @Override
    public void onMessageUpload(List<Message> list) {
        try {
            OkHttpClient mOkHttpClient = new OkHttpClient();
            final String requestUrl = "http://" + BaseUrl.BASE_IP + "/Dfriend/MsgCon";
            Log.i("INFO", "Request Url: " + requestUrl);
            //.replace("\\", "")
            String json = list.toString();
            Log.e("TAG", json);
            RequestBody requestBody = new FormEncodingBuilder()
                    .add("e.JsonStr", json)
                    .build();
            final Request request = new Request.Builder()
                    .url(requestUrl)
                    .post(requestBody) // post json提交
                    .build();
            Call call = mOkHttpClient.newCall(request);
            //执行请求
            Response response = call.execute();
            //请求执行成功
            String jsonContext = response.body().string();
            Log.e("TAG" , jsonContext);
            //获取返回数据 可以是String，bytes ,byteStream
            CodeBean entity = JSON.parseObject(jsonContext , new TypeReference<CodeBean>() {});
            if (response.isSuccessful() && entity.getCode() == 0) {
                if (part == 0) {
                    //为了防止上传失败 ，做的标识
                    if (PreferenceHelper.getBoolean("partUploadMessageFailure", false)) {
                        PreferenceHelper.commitBoolean("partUploadMessageFailure", false);
                    }
                }
                Log.e("TAG", "上传成功...");
            } else {
                if (homePresenter != null) {
                    homePresenter.onMessageFailure(courrPart);
                }
                if (part == 0) {
                    PreferenceHelper.commitBoolean("partUploadMessageFailure", true);
                }
            }
        } catch (Exception e) {
            if ( part == 0 ) {
                PreferenceHelper.commitBoolean("partUploadMessageFailure", true);
            }
            Log.e("TAG" , e.getMessage());
        } finally {
            if (courrPart < part && part != 0) {
                messagesAll.subList(0, pointsDataLimit).clear();
                courrNumber = messagesAll.size();
                //多次上传
                courrPart++;
            } else {
                if (homePresenter != null && courrPart == part) {
                    homePresenter.uploadResponse();
                }
            }
        }
    }
}
